package net.zdsoft.wpchat.support.client;

import java.util.HashMap;
import java.util.List;

import javax.servlet.http.HttpServletRequest;

import net.zdsoft.keel.action.ActionContext;
import net.zdsoft.keel.util.URLUtils;
import net.zdsoft.keel.util.Validators;
import net.zdsoft.wpchat.support.entity.AuthModule;
import net.zdsoft.wpchat.support.entity.UserCatalog;
import net.zdsoft.wpchat.support.entity.UserConfig;
import net.zdsoft.wpchat.support.entity.UserModule;
import net.zdsoft.wpchat.support.entity.UserOperation;
import net.zdsoft.wpchat.support.util.PageUtils;

/**
 * 用户权限模块
 *
 * @author xuan
 */
public class UserAuth {
    public static final String KEY = "net.zdsoft.wpchat.support.client.UserAuth";

    private final UserOperation userOperation;
    private final UserConfig userConfig;
    private final UserCatalog userCatalog;
    private final UserModule userModule;

    private final HashMap<String, Boolean> externalConditions = new HashMap<String, Boolean>();

    public UserAuth(UserConfig userConfig, UserOperation userOperation) {
        this.userOperation = userOperation;
        this.userConfig = userConfig;
        userModule = userOperation.getUserModule();
        userCatalog = userModule.getUserCatalog();
    }

    public boolean canVisit(String actionName) {
        return userConfig.getUserOperation(userCatalog.getCatalog().getNamespace(), actionName) != null;
    }

    public boolean canDo(String operationName) {
        return userModule.getUserOperation(operationName) != null;
    }

    public boolean canAdd() {
        return canDo("add");
    }

    public boolean canRemove() {
        return canDo("remove");
    }

    public boolean canModify() {
        return canDo("modify");
    }

    public boolean isAll() {
        return userModule.getDefaultUserOperation().isPermissionAll();
    }

    public boolean isAuthSchool() {
        return userModule.getDefaultUserOperation().isPermissionAuth();
    }

    public boolean isArea() {
        return userModule.getDefaultUserOperation().isPermissionArea();
    }

    public String drawNavigator() {
        StringBuffer navigator = new StringBuffer();
        navigator.append("<div id=\"navigator\">");
        navigator.append(userCatalog.getCatalog().getName());
        navigator.append(" &gt;&gt; ");
        navigator.append(userModule.getModule().getName());
        navigator.append("</div>");
        return navigator.toString();
    }

    public String drawNavigator(HttpServletRequest request) {
        StringBuffer navigator = new StringBuffer();
        navigator.append("<div id=\"navigator\">");
        navigator.append(userCatalog.getCatalog().getName());
        navigator.append(" &gt;&gt; ");
        navigator.append(userModule.getModule().getName());
        navigator.append("</div>");

        navigator.append("<div id=\"logininfo\">");
        navigator.append("Your IP is &nbsp;:&nbsp; ").append(request.getRemoteAddr())
                .append(" &nbsp; &nbsp; | &nbsp; &nbsp; ");
        MemoryUser user = (MemoryUser) request.getSession().getAttribute(MemoryUser.KEY);
        if (user != null) {
            navigator.append("You are logged in as &nbsp;:&nbsp; ").append(user.getUsername())
                    .append(" [ " + user.getRealName()).append(" ] &nbsp; &nbsp; | &nbsp; &nbsp; ");
        }
        else {
            navigator.append("You are logged in as &nbsp;:&nbsp; ").append("- [ -")
                    .append(" ] &nbsp; &nbsp; | &nbsp; &nbsp; ");

        }
        navigator.append("<a href=\"../frame/password.htm\">Change Password</a> " + "&nbsp; &nbsp; | &nbsp; &nbsp; ");
        navigator.append("<a href=\"../frame/welcome.htm\">Welcome</a>" + " &nbsp; &nbsp; | &nbsp; &nbsp; ");
        navigator.append("<a href=\"../frame/supportLogout.htm\" target=\"_top\">Logout</a>");
        navigator.append("</div>");

        return navigator.toString();
    }

    public void addCondition(String conditionName, boolean result) {
        externalConditions.put(conditionName, new Boolean(result));
    }

    public String drawTitle(String schoolId) {
        StringBuffer title = new StringBuffer();
        title.append("<div id=\"titleMain\">\n");

        final int maxModuleCountOfLine = 8;
        List<UserModule> userModules = userCatalog.getUserModuleList();
        for (int i = 0, c = 0; i < userModules.size(); i++) {
            UserModule brotherModule = userModules.get(i);
            AuthModule authModule = brotherModule.getModule();

            if (!authModule.isVisible()) {
                continue;
            }

            if (c++ % maxModuleCountOfLine == 0) {
                title.append("  <div class=\"modules\">\n");
            }

            String[] params = authModule.getParameters();
            String[] values = new String[params.length];

            boolean isUnusable = judgeUnusable(schoolId, brotherModule, authModule, params, values);

            // 参数不足的模块
            if (isUnusable) {
                title.append("    <div class=\"unusable\">");
                title.append(brotherModule.getModule().getName());
                title.append("</div>\n");
            }
            else {
                String moduleTarget = PageUtils.getModuleTarget(brotherModule.getDefaultUserOperation());

                if (params.length > 0) {
                    for (int j = 0; j < params.length; j++) {
                        String param = params[j];
                        if (param.startsWith(AuthModule.CHIOCE_FLAG)) {
                            param = param.substring(1);
                        }
                        if (!authModule.isNoLinkType()) {
                            moduleTarget = URLUtils.addQueryString(moduleTarget, param, values[j]);
                        }
                    }
                }

                title.append("    ");

                if (!authModule.isNoLinkType()) {
                    title.append("<a href=\"");
                    title.append(moduleTarget);
                    title.append("\">");
                }

                title.append("<div ");
                if (brotherModule == userModule) {// 当前模块
                    title.append("id=\"current\"");
                }
                else {
                    title.append("class=\"other\"");
                }
                title.append(">");
                title.append(brotherModule.getModule().getName());
                title.append("</div>");

                if (!authModule.isNoLinkType()) {
                    title.append("</a>");
                }

                title.append("\n");
            }

            if (c == userModules.size() || c % maxModuleCountOfLine == 0) {
                title.append("  </div>\n");
            }
        }

        title.append("</div>");

        return title.toString();
    }

    public String drawTitle() {
        return drawTitle(null);
    }

    /**
     * 判断当前模块是否可用，并从request中获取指定参数.
     */
    private boolean judgeUnusable(String schoolId, UserModule brotherModule, AuthModule authModule, String[] params,
            String[] values) {
        HttpServletRequest request = ActionContext.getRequest();
        boolean isUnusable = false;

        if (userModule.getModule().isNoCarryParametersType() && brotherModule != userModule) {
            for (int j = 0; j < params.length; j++) {
                if (!params[j].startsWith(AuthModule.CHIOCE_FLAG)) {
                    isUnusable = true;
                }
            }
            if (isUnusable) {
                return isUnusable;
            }
        }

        for (int j = 0; j < params.length; j++) {
            if (params[j].startsWith(AuthModule.CHIOCE_FLAG)) {
                String value = request.getParameter(params[j].substring(1));
                values[j] = value;
            }
            else {
                String value = request.getParameter(params[j]);
                if (Validators.isEmpty(value)) {
                    isUnusable = true;
                    break;
                }
                else {
                    values[j] = value;
                }
            }
        }

        if (!isUnusable && brotherModule != userModule) {
            // 判断外部条件是否充足
            String[] conditions = authModule.getConditions();
            if (Validators.isEmpty(schoolId)) {
                for (int j = 0; j < conditions.length; j++) {
                    Boolean result = externalConditions.get(conditions[j]);
                    if (result == null || !result.booleanValue()) {
                        isUnusable = true;
                    }
                }
            }
            else {
                for (int j = 0; j < conditions.length; j++) {
                    if ("hasFamilyPhoneService".equals(conditions[j])) {
                        // ServiceLocator.getInstance().getFeeServiceBean()
                        // .hasServiceItem(schoolId,
                        // ServiceItemTypeEnum.FAMILYPHONE);
                    }
                    else {
                        Boolean result = externalConditions.get(conditions[j]);
                        if (result == null || !result.booleanValue()) {
                            isUnusable = true;
                        }
                    }
                }
            }

        }
        return isUnusable;
    }

    public UserConfig getUserConfig() {
        return userConfig;
    }

    public UserOperation getUserOperation() {
        return userOperation;
    }

}
